using System;
using System.Collections.Generic;
using System.Web.UI;
using System.Web.UI.HtmlControls;
using System.Web.UI.WebControls;
using ComDevFx.Arch.Base.Persister.NH.Burrow.WebUtil.Exceptions;

namespace ComDevFx.Arch.Base.Persister.NH.Burrow.WebUtil.Impl
{
    public class GlobalPlaceHolder
    {
        /*
         * DateTime:  2011.07.05
         * change log code flag: 201107030201
         * modify user: tang heng jie
         */
        //original code:
        //private const string holderId = "ComDevFx.Arch.Base.Persister.NH.Burrow.WebUtil.GlobalPlaceHolder";

        //Modified as:
        private const string holderId = "NHibernate_Burrow_WebUtil_GlobalPlaceHolder";

        private const string UpdatePanelId = "ComDevFx.Arch.Base.Persister.NH.Burrow.WebUtil.GlobalPlaceHolderUpdatePanel";
        /*
         * DateTime:  2011.07.05
         * change log code flag: 201107030202
         * modify user: tang heng jie
         */
        //original code:
        //private readonly Control holder;

        //modified as:
        private Control holder;

     
        private readonly Page page;
        private UpdatePanel up;

        public GlobalPlaceHolder(Page p)
        {
            this.page = p;
            holder = new PlaceHolder();
            holder.ID = holderId;
            p.Init += new EventHandler(p_Init);
            p.PreRender += new EventHandler(p_PreRender);
        }

        void p_Init(object sender, EventArgs e)
        {
            if (IsInAjaxMode())
            {
                up = new UpdatePanel();
                up.ID = UpdatePanelId;
                up.UpdateMode = UpdatePanelUpdateMode.Always;
                page.Form.Controls.Add(up);
            }
        }

        void p_PreRender(object sender, EventArgs e)
        {
            if (IsInAjaxMode())
            {
                up.ContentTemplateContainer.Controls.Add(holder);
            }
            else
            {
                if (page.Form == null)
                    return; //for a page without form, there is no way to track status, and thus no need for this holder to be placed.

                /*
                 * DateTime:  2011.07.05
                 * change log code flag: 201107030201
                 * modify user: tang heng jie
                 */
                //the origin code:
                //page.Form.Controls.Add(holder);

                //modified as:
                PlaceHolder existedHolder = page.FindControl(holderId) as PlaceHolder;
                if (existedHolder == null)
                {
                    page.Form.Controls.Add(holder);
                }
                else
                {
                    for (int i = holder.Controls.Count - 1; i >= 0; i--)
                    {
                        Control theControl = holder.Controls[i];
                        holder.Controls.Remove(theControl);
                        existedHolder.Controls.Add(theControl);
                    }
                    holder = existedHolder;
                }
            }
        }


        private bool IsInAjaxMode()
        {
            ScriptManager current = ScriptManager.GetCurrent(page);
            if (current != null && current.EnablePartialRendering)
            {
                return true;
            }
            return false;
        }

        public void AddPostBackFields(IDictionary<String, string> fields)
        {
            foreach (KeyValuePair<string, string> pair in fields)
            {
                AddPostBackField(pair.Key, pair.Value);
            }
        }

        public void AddPostBackField(string key, string val)
        {
            if (!string.IsNullOrEmpty(val))
            {
                Literal l = new Literal(); //use literal instead of HiddenField to precisely control Id and name
                l.Text = string.Format("<input type='hidden' Name='{0}' ID='{0}' value='{1}' />", key, val);
                holder.Controls.Add(l);
            }
        }
    }
}